package com.margo.rabbit.direct;


import java.io.IOException;
import java.util.concurrent.TimeoutException;

import com.rabbitmq.client.Channel;
import com.rabbitmq.client.ConfirmListener;
import com.rabbitmq.client.Connection;
import com.rabbitmq.client.ConnectionFactory;
import com.rabbitmq.client.ReturnListener;
import com.rabbitmq.client.AMQP.BasicProperties;

/**
 * direct 生产者
 * @author fangxingbang
 * https://www.cnblogs.com/vipstone/p/9295625.html
 *
 */
public class MargoRabbitDirectProducer {
	public static void main(String[] args) throws IOException, TimeoutException {
		directDefaultExchange();
		//directDefaultExchangeBatch();
	}
	
	/**
	 * default模式  默认 不申明交换器
	 * @throws IOException
	 * @throws TimeoutException
	 */
	public static void directDefaultExchange() throws IOException, TimeoutException {
		String queueName="margo-direct";
		
		ConnectionFactory connectionFactory=new ConnectionFactory();
		connectionFactory.setHost("127.0.0.1");
		Connection connection=connectionFactory.newConnection();
		Channel channel=connection.createChannel();
		//申明队列
		channel.queueDeclare(queueName, false, false, false, null);
		channel.confirmSelect();
		channel.addConfirmListener(new ConfirmListener() {
			@Override
			public void handleNack(long deliveryTag, boolean multiple) throws IOException {
				System.out.println("失败");
			}
			@Override
			public void handleAck(long deliveryTag, boolean multiple) throws IOException {
				System.out.println("成功");
			}
		});
		/**
		 * 	https://www.jianshu.com/p/b8416617e869
		 * This flag tells the server how to react if the message cannot be routed to a queue.
		 * if this flag is set,the server will return an unroutable message with a return method.
		 * if this flag is zero,the server silently drops the message
		 * 	如果mandatory有设置，则当消息不能路由到队列中去的时候，会触发return method。
		 * 	如果mandatory没有设置，则当消息不能路由到队列的时候，server会删除该消息。
		 */
		channel.addReturnListener(new ReturnListener() {
			//如果rabbitMQ中没有margo-direct队列，则走这里
			@Override
			public void handleReturn(int arg0, String arg1, String arg2, String arg3, BasicProperties arg4, byte[] arg5)
					throws IOException {
				System.out.println("return");
			}
		});
		/**
		 * The default exchange is implicitly bound to every queue, 
		 * with a routing key equal to the queue name. 
		 * It is not possible to explicitly bind to, or unbind from the default exchange. 
		 * It also cannot be deleted.
		 */
		//路由键跟队列名称相同
		channel.basicPublish("", queueName, true, null, "margo".getBytes());
	}
	
	/**
	 * default模式  默认 不申明交换器
	 * @throws IOException
	 * @throws TimeoutException
	 */
	public static void directDefaultExchangeBatch() throws IOException, TimeoutException {
		String queueName="margo-direct";
		
		ConnectionFactory connectionFactory=new ConnectionFactory();
		connectionFactory.setHost("127.0.0.1");
		Connection connection=connectionFactory.newConnection();
		Channel channel=connection.createChannel();
		//申明队列
		channel.queueDeclare(queueName, false, false, false, null);
		channel.confirmSelect();
		channel.addConfirmListener(new ConfirmListener() {
			@Override
			public void handleNack(long deliveryTag, boolean multiple) throws IOException {
				System.out.println("失败");
			}
			@Override
			public void handleAck(long deliveryTag, boolean multiple) throws IOException {
				System.out.println("成功");
			}
		});
		/**
		 * 	https://www.jianshu.com/p/b8416617e869
		 * This flag tells the server how to react if the message cannot be routed to a queue.
		 * if this flag is set,the server will return an unroutable message with a return method.
		 * if this flag is zero,the server silently drops the message
		 * 	如果mandatory有设置，则当消息不能路由到队列中去的时候，会触发return method。
		 * 	如果mandatory没有设置，则当消息不能路由到队列的时候，server会删除该消息。
		 */
		channel.addReturnListener(new ReturnListener() {
			//如果rabbitMQ中没有margo-direct队列，则走这里
			@Override
			public void handleReturn(int arg0, String arg1, String arg2, String arg3, BasicProperties arg4, byte[] arg5)
					throws IOException {
				System.out.println("return");
			}
		});
		/**
		 * The default exchange is implicitly bound to every queue, 
		 * with a routing key equal to the queue name. 
		 * It is not possible to explicitly bind to, or unbind from the default exchange. 
		 * It also cannot be deleted.
		 */
		for(int i=0;i<100;i++) {
			//路由键跟队列名称相同
			channel.basicPublish("", queueName, true, null, "margo".getBytes());
		}
	}
}
